/*
  Copyright (C) 2011, Kyungjoo Kim
  
  This file is part of UHM (Unassembled HyperMatrix) sparse direct solver.
  
  All rights reserved.

  This library is free software; you can redistribute it and/or
  modify it under the terms of the GNU Lesser General Public
  License as published by the Free Software Foundation; either
  version 2.1 of the License, or (at your option) any later version.
  
  This library is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY; without even the implied warranty of
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  Lesser General Public License for more details.
  
  You should have received a copy of the GNU Lesser General Public
  License along with this library; if not, write to the Free Software
  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
  Also add information on how to contact you by electronic and paper mail.
  
  
  Kyungjoo Kim
  iamkyungjoo@gmail.com
*/
#ifndef UHM_OPERATION_MESH_HXX
#define UHM_OPERATION_MESH_HXX

namespace uhm {
  // Var 1 :: Heavy edge matching
  // Var 2 :: Metis graph partitioning
  // Var 3 :: Metis nested dissection
  extern bool build_graph           (std::vector< Element > *orphan,
                                     Element parent,
                                     //                         
                                     std::vector< int > *xadj,
                                     std::vector< int > *adjncy,
                                     std::vector< int > *adjwgt);
  
  // ** front end
  extern bool build_tree            (Mesh m);
  extern bool partition_mesh        (Mesh m, int nparts);

  // ** various implementations
  extern bool build_tree_var_1      (Mesh m);
  extern bool build_tree_var_2      (Mesh m);
  extern bool build_tree_var_2      (Mesh m, int nparts);
  extern bool build_tree_var_3      (Mesh m);
  extern bool build_tree_var_4      (Mesh m);
  extern bool build_tree_var_5      (Mesh m);

  extern bool partition_mesh_var_1  (Mesh m, int nparts);
  extern bool partition_mesh_var_2  (Mesh m, int nparts);


  // ** pragma wrapper
  extern void decompose_with_free   (Mesh m);
  extern void decompose_without_free(Mesh m);
  extern void solve_1               (Mesh m);
  extern void solve_2               (Mesh m);
  extern void solve                 (Mesh m);
  extern void check_1               (Mesh m);
  extern void check_2               (Mesh m);
  extern void check                 (Mesh m);

  extern void decompose_with_free   (Mesh m, int decomposition);
  extern void decompose_without_free(Mesh m, int decomposition);
  extern void solve_1               (Mesh m, int decomposition);
  extern void solve_2               (Mesh m, int decomposition);
  extern void solve                 (Mesh m, int decomposition);
  extern void check_1               (Mesh m, int decomposition);
  extern void check_2               (Mesh m, int decomposition);
  extern void check                 (Mesh m, int decomposition);
}


#endif
